Skip to content

fix(artifact): a bare value flag is refused by name, not written as "true" or 1 - #283

Merged
StepenkoAnatoli merged 1 commit into
mainfrom
claude/artifact-bare-values-20261011
Oct 11, 2026
Merged

StepenkoAnatoli merged 1 commit into
mainfrom
claude/artifact-bare-values-20261011

Conversation

@StepenkoAnatoli

Copy link
Copy Markdown
Owner

Fixes #280.

What changed

bin/artifact.mjs runs checkFlagValues right after each command's unknown-flag refusal, from one VALUE_FLAGS table. validate checks --file and --expect-client-ref; create checks every value flag for a value and --run-id / --run-attempt as whole numbers of at least 1. A bare flag is --<name> needs a value, exit 3, before anything is read or written. Two tests in artifact-cli.test.mjs; README inventory 1787 → 1789; docs/ARCHITECTURE.md row and CHANGELOG bullet in the same commit.

Why

parseFlags reads a bare flag as true, and create only asked whether a required flag was present. create --ref --run-id --output exited 0, wrote a package literally named true with ref: "true" and workflowRunId: 1 in its manifest, and reported re-validated after writing: PASS. Invented provenance that nothing downstream could tell from real. Same bug class as #269 and #270, same remedy.

Verified

  • Red first: selftest.mjs artifact-cli 20 passed, 2 failed with only the tests in place.
  • After the fix: 22 passed, 0 failed.
  • Full offline suite on Node 24.21.0 linux: 1789 passed, 0 failed, 203.5 s.
  • By hand from an empty folder: the three bare flags refused by name, exit 3, folder empty; --run-id 12x refused by name; validate --file refused by name; a real create still writes its package and exits 0.
  • git diff --check clean; five files LF-only.

Untested

This PR's all-seven CI.

🤖 Generated with Claude Code

https://claude.ai/code/session_01Gg4isLfN2Ng16zr5DwTnH9


Generated by Claude Code

…true" or 1

What changed: bin/artifact.mjs imports checkFlagValues and runs it right after each command's refuseUnknownFlags, from one VALUE_FLAGS table: validate checks --file and --expect-client-ref; create checks --root, --output, --client-ref, --repository, --ref, --commit, --workflow, --run-url, --html-url and --api-version for a value, and --run-id and --run-attempt as whole numbers of at least 1. A bare flag is "--<name> needs a value", exit 3 (EXIT.BLOCKED); a non-number run id is "--run-id must be a whole number of at least 1, not "12x"", where writeArtifact had refused it later with its own wording. Two tests in artifact-cli.test.mjs: create with each of --ref, --run-id and --output bare, in its own empty working folder, exits 3, names the flag first and leaves the folder empty; validate --file bare exits 3 by name with no ZIP-READ. README inventory 1787 to 1789.

Why: parseFlags reads a flag with no value as `true`, and create's "needs" check only asked whether a required flag was PRESENT (flags[name] === undefined). So `create --ref --run-id --output` exited 0, wrote a package literally named "true" whose manifest carried ref "true", workflowRunId 1 and run URLs ending in /runs/1, and reported "re-validated after writing: PASS" - invented provenance that nothing downstream could tell from real; validate --file bare opened a file called "true" and reported ZIP-READ ENOENT (#280, found 2026-10-11 while scanning the CLIs for the shape of #269 and #270). Alternative set aside: a `=== true` check beside each read - twelve home-made checks beside the validator that exists for this. No ADR: a bug fix with one obvious remedy, the same one #269 and #270 took.

What it touched: research-kit/bin/artifact.mjs (the import, the VALUE_FLAGS table, two checkFlagValues calls); research-kit/test/artifact-cli.test.mjs (two tests); research-kit/README.md (the inventory line, 1789); docs/ARCHITECTURE.md (the artifact.mjs row gains the clause); CHANGELOG.md (Unreleased). No new flag, format, key or check; the documented flags and their defaults are unchanged.

What you verified:
- verified: red first - with only the tests in place, `node research-kit/bin/selftest.mjs artifact-cli` from the repository root: 20 passed, 2 failed - create "expected a refusal, got exit 0 ... wrote p.zip", validate --file bare not refused by name. Node 24.21.0 linux.
- verified: after the fix, the same group: 22 passed, 0 failed, 5.0 s.
- verified: by hand from an empty folder - `create --repository o/r --ref --commit <40 hex> --workflow w.yml --run-id --output` prints "--output needs a value", "--ref needs a value", "--run-id needs a value", exit 3, folder empty; `--run-id 12x` -> "--run-id must be a whole number of at least 1", exit 3; `validate --file` -> "--file needs a value", exit 3; the same create with real values still writes p.zip and exits 0.
- verified: the full offline suite from the repository root on Node 24.21.0 linux: 1789 passed, 0 failed, 0 unsupported, 203.5 s, exit 0.
- verified: git diff --check clean; the five files LF-only.
- untested when written: this commit's all-seven CI, and the installed commit gate (not installed in this container; the suite was run by hand instead).

What you got wrong and fixed: nothing to report.

Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01Gg4isLfN2Ng16zr5DwTnH9
@StepenkoAnatoli
StepenkoAnatoli marked this pull request as ready for review October 11, 2026 10:16
@StepenkoAnatoli
StepenkoAnatoli merged commit 8698576 into main Oct 11, 2026
7 checks passed
@StepenkoAnatoli
StepenkoAnatoli deleted the claude/artifact-bare-values-20261011 branch October 11, 2026 21:43
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

artifact: create with a bare --ref, --run-id, --output (and the other value flags) writes "true" and 1 into a package that validates

1 participant